home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Atari Mega Archive 2
/
Atari Mega Archive CD - Volume 2.iso
/
minix
/
up1510b.tgz
/
up1510b
/
src
/
commands
/
nroff
/
low.c
< prev
next >
Wrap
C/C++ Source or Header
|
1990-07-23
|
12KB
|
877 lines
/*
* low.c - misc low-level functions for nroff word processor
*
* adapted for atariST/TOS by Bill Rosenkranz 11/89
* net: rosenkra@hall.cray.com
* CIS: 71460,17
* GENIE: W.ROSENKRANZ
*
* original author:
*
* Stephen L. Browning
* 5723 North Parker Avenue
* Indianapolis, Indiana 46220
*
* history:
*
* - Originally written in BDS C;
* - Adapted for standard C by W. N. Paul
* - Heavily hacked up to conform to "real" nroff by Bill Rosenkranz
* - Adapted to have it recognize also VT100 escape codes (e.g. ESC[7m)
* by Wim 'Blue Baron' van Dorst (wsincc@tuerc3.urc.tue.nl)
*/
#undef NRO_MAIN /* extern globals */
#include <stdio.h>
#include "nroff.h"
/*------------------------------*/
/* atod */
/*------------------------------*/
atod (c)
char c;
{
/*
* convert ascii character to decimal.
*/
return (((c < '0') || (c > '9')) ? -1 : c - '0');
}
/*------------------------------*/
/* robrk */
/*------------------------------*/
robrk ()
{
/*
* end current filled line
*/
if (co.outp > 0)
{
#ifdef GEMDOS
co.outbuf[co.outp] = '\r';
co.outbuf[co.outp+1] = '\n';
co.outbuf[co.outp+2] = EOS;
#else
co.outbuf[co.outp] = '\n';
co.outbuf[co.outp+1] = EOS;
co.outbuf[co.outp+2] = EOS;
#endif
put (co.outbuf);
}
co.outp = 0;
co.outw = 0;
co.outwds = 0;
co.outesc = 0;
}
/*------------------------------*/
/* ctod */
/*------------------------------*/
ctod (p)
register char *p;
{
/*
* convert string to decimal.
* processes only positive values.
*/
register int val;
register int d;
val = 0;
while (*p != EOS)
{
d = atod (*p);
p++;
if (d == -1)
return (val);
val = 10 * val + d;
}
return (val);
}
/*------------------------------*/
/* inptobu */
/*------------------------------*/
inptobu (ps)
char *ps;
{
/*
* convert input units to b.u.
*/
return;
}
/*------------------------------*/
/* butochar */
/*------------------------------*/
butochar (ps)
char *ps;
{
/*
* convert b.u. to char spaces
*/
return;
}
/*------------------------------*/
/* skipbl */
/*------------------------------*/
char *skipbl (p)
register char *p;
{
/*
* skip blanks and tabs in character buffer. return ptr to first
* non-space or non-tab char. this could mean EOS or \r or \n.
* also increments the arg ptr (side effect).
*/
while ((*p != EOS) && (*p == ' ' || *p == '\t'))
++p;
return (p);
}
/*------------------------------*/
/* skipwd */
/*------------------------------*/
char *skipwd (p)
register char *p;
{
/*
* skip over word and punctuation. anything but space,\t,\r,\n, and EOS
* is skipped. return ptr to the first of these found. also increments
* the arg ptr (side effect).
*/
while (*p != ' ' && *p != '\t' && *p != '\r' && *p != '\n' && *p != EOS)
++p;
return (p);
}
/*------------------------------*/
/* space */
/*------------------------------*/
space (n)
int n;
{
/*
* space vertically n lines. this does header and footer also.
*/
robrk ();
if (pg.lineno > pg.bottom)
return;
if (pg.lineno == 0)
phead ();
skip (min (n, pg.bottom + 1 - pg.lineno));
pg.lineno += n;
set_ireg ("ln", pg.lineno, 0);
if (pg.lineno > pg.bottom)
pfoot ();
}
/*------------------------------*/
/* getfield */
/*------------------------------*/
char *getfield (p, q, delim)
register char *p;
register char *q;
char delim;
{
/*
* get field from title
*/
while (*p != delim && *p != '\r' && *p != '\n' && *p != EOS)
{
*q++ = *p++;
}
*q = EOS;
if (*p == delim)
++p;
return (p);
}
/*------------------------------*/
/* getwrd */
/*------------------------------*/
getwrd (p0, p1)
register char *p0;
register char *p1;
{
/*
* get non-blank word from p0 into p1.
* return number of characters processed.
*/
register int i;
register char *p;
char c;
/*
* init counter...
*/
i = 0;
/*
* skip leading whitespace
*/
while (*p0 && (*p0 == ' ' || *p0 == '\t'))
{
++i;
++p0;
}
/*
* set ptr and start to look for end of word
*/
p = p0;
while (*p0 != ' ' && *p0 != EOS && *p0 != '\t')
{
if (*p0 == '\n' || *p0 == '\r')
break;
*p1 = *p0++;
++p1;
++i;
}
c = *(p1 - 1);
if (c == '"')
c = *(p1 - 2);
if (c == '?' || c == '!')
{
*p1++ = ' ';
++i;
}
if (c == '.' && (*p0 == '\n' || *p0 == '\r' || islower (*p)))
{
*p1++ = ' ';
++i;
}
*p1 = EOS;
return (i);
}
/*------------------------------*/
/* countesc */
/*------------------------------*/
#define ESC 27
countesc (p)
register char *p;
{
/*
* count escape sequence characters in given null-terminated
* string
*/
register char *pp;
register int num;
pp = p;
num = 0;
while (*pp != EOS)
{
if (*pp == ESC)
{
/*
* count escape char (vt52 and vt100)
*/
switch (*(pp+1))
{
case 'A': /* ESC-a */
case 'B':
case 'C':
case 'D':
case 'E':
case 'H':
case 'I':
case 'J':
case 'K':
case 'L':
case 'M':
case 'd':
case 'e':
case 'f':
case 'j':
case 'k':
case 'l':
case 'o':
case 'p':
case 'q':
case 'v':
case 'w':
num += 2;
break;
case 'b': /* ESC-a-b */
case 'c':
num += 3;
break;
case 'Y': /* ESC-a-b-c */
case '[': /* Esc [ 7 m */
num += 4;
break;
default:
num += 1;
break;
}
}
pp++;
}
return (num);
}
/*------------------------------*/
/* itoda */
/*------------------------------*/
itoda (value, p, size)
int value;
register char *p;
register int size;
{
/*
* convert integer to decimal ascii string
*/
register int i;
register int j;
register int k;
register int aval;
char c[20];
aval = abs (value);
c[0] = EOS;
i = 1;
do
{
c[i++] = (aval % 10) + '0';
aval /= 10;
} while (aval > 0 && i <= size);
if (value < 0 && i <= size)
c[i++] = '-';
for (j = 0; j < i; ++j)
*p++ = c[i - j - 1];
return (i);
}
/*------------------------------*/
/* itoROMAN */
/*------------------------------*/
itoROMAN (value, p, size)
int value;
register char *p;
register int size;
{
/*
* convert integer to upper roman. must be positive
*/
register int i;
register int j;
register int k;
register int aval;
char c[100];
int rem;
aval = abs (value);
c[0] = EOS;
i = 1;
/*
* trivial case:
*/
if (aval == 0)
{
c[i++] = '0';
goto done_100;
}
/*
* temporarily mod 100...
*/
aval = aval % 100;
if (aval > 0)
{
/*
* build backward
*
* | I| 1
* | II| 2
* | III| 3
* | VI| 4
* | V| 5
* | IV| 6
* | IIV| 7
* | IIIV| 8
* | XI| 9
* | X| 0
* | IX| 11
* | IIX| 12
*/
if ((aval % 5 == 0) && (aval % 10 != 0))/* 5 */
c[i++] = 'V';
else
{
rem = aval % 10;
if (rem == 9) /* 9 */
{
c[i++] = 'X';
c[i++] = 'I';
}
else if (rem == 8) /* 8 */
{
c[i++] = 'I';
c[i++] = 'I';
c[i++] = 'I';
c[i++] = 'V';
}
else if (rem == 7) /* 7 */
{
c[i++] = 'I';
c[i++] = 'I';
c[i++] = 'V';
}
else if (rem == 6) /* 6 */
{
c[i++] = 'I';
c[i++] = 'V';
}
else if (rem == 4) /* 4 */
{
c[i++] = 'V';
c[i++] = 'I';
}
else /* 3,2,1 */
{
for (j = 0; j < rem; j++)
c[i++] = 'I';
}
}
aval /= 10;
if (aval == 0)
goto done_100;
rem = aval % 10;
if (rem == 4)
{
c[i++] = 'L';
c[i++] = 'X';
}
else if (rem == 5)
{
c[i++] = 'L';
}
else if (rem < 4)
{
for (j = 0; j < rem; j++)
c[i++] = 'X';
}
else
{
for (j = 0; j < rem - 5; j++)
c[i++] = 'X';
c[i++] = 'L';
}
}
done_100:
/*
* divide by 100 (they are done) and temp mod by another 10
*/
aval = abs (value);
aval /= 100;
if (aval > 0)
{
rem = aval % 10;
if (rem == 4)
{
c[i++] = 'D';
c[i++] = 'C';
}
if (rem == 5)
{
c[i++] = 'D';
}
else if (rem < 4)
{
for (j = 0; j < rem; j++)
c[i++] = 'C';
}
else if (rem == 9)
{
c[i++] = 'M';
c[i++] = 'C';
}
else if (rem < 9)
{
for (j = 0; j < rem - 5; j++)
c[i++] = 'C';
c[i++] = 'D';
}
}
aval /= 10;
if (aval > 0)
{
rem = aval